﻿
Imports std
Imports nodes_t = std.hashmapless(Of System.Int64, osi.fs.node, _16383, _int64_to_uint32)

Partial Public Class fs
    Private Shared ReadOnly nodes As nodes_t = Nothing
    Private Shared ReadOnly root As node = Nothing
    Private Shared ReadOnly next_node_id As next_id = Nothing

    Shared Sub New()
        nodes = New nodes_t()
        next_node_id = New next_id()
        root = New node(0)
        assert(add_node(root))
    End Sub

    Private Shared Function waitfor_initialized() As Boolean
        Return root.waitfor_initialized()
    End Function

    Friend Shared Function add_node(ByVal n As node) As Boolean
        If n Is Nothing Then
            Return False
        Else
            Return nodes.unique_insert(n.id, n)
        End If
    End Function

    Private Shared Function waitfor_initialized(ByVal d As _do(Of Boolean)) As eventComb
        assert(Not d Is Nothing)
        Return New eventComb(Function() As Boolean
                                 Return waitfor_initialized() AndAlso
                                        goto_next()
                             End Function,
                             Function() As Boolean
                                 Return d() AndAlso
                                        goto_end()
                             End Function)
    End Function

    Private Shared Function create_node() As node
        Return New node(next_node_id.next())
    End Function

    Public Shared Function add(ByVal node As pointer(Of node)) As eventComb
        Return waitfor_initialized(Function() As Boolean
                                       Dim n As node = Nothing
                                       n = create_node()
                                       Return add_node(n) AndAlso eva(node, n)
                                   End Function)
    End Function

    Private Shared Function get_node(ByVal id As Int64, ByRef n As node) As Boolean
        If nodes.get(id, n) Then
            assert(Not n Is Nothing)
            assert(id = n.id)
            Return True
        Else
            Return False
        End If
    End Function

    Public Shared Function [get](ByVal id As Int64, ByVal p As pointer(Of node)) As eventComb
        Return waitfor_initialized(Function() As Boolean
                                       Dim n As node = Nothing
                                       Return get_node(id, n) AndAlso eva(p, n)
                                   End Function)
    End Function

    Public Shared Function [erase](ByVal id As Int64) As eventComb
        Return waitfor_initialized(Function() As Boolean
                                       Dim n As node = Nothing
                                       If get_node(id, n) Then
                                           n.destroy()
                                           Return nodes.erase(id)
                                       Else
                                           Return False
                                       End If
                                   End Function)
    End Function
End Class
